package utilidades;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Vector;
import java.util.logging.Level;
import java.util.logging.Logger;

/**
 * Clase controladora de la persistencia (Base de datos ACCESS)
 *
 * @version 1.0
 * @author Grupo GM10
 */
public class Agente {

	// Instancia del agente
	protected static Agente mInstancia = null;
	// Conexion con la base de datos
	protected static Connection mBD;
	// Identificador ODBC de la base de datos
	// Driven para conectar con bases de datos Microsoft Access
	private static final String driver = "org.sqlite.JDBC";

	// Constructor
	private Agente() throws Exception {
		conectar();

	}

	// Implementacion del patron singleton
	// Este patron de diseño permite implementar clases de las cuales
	// solo existir una instancia
	// http://es.wikipedia.org/wiki/Singleton
	/**
	 * Metodo constructor segun patron Singleton
	 *
	 * @return mInstancia Instancia patron Singleton
	 * @throws Exception
	 */
	public static Agente getAgente() {
		if (mInstancia == null) {
			try {
				mInstancia = new Agente();
			} catch (Exception ex) {
				Logger.getLogger(Agente.class.getName()).log(Level.SEVERE,
						null, ex);
			}
		}
		return mInstancia;
	}

	/**
	 * Conexion a base de datos
	 *
	 * @throws Exception
	 */
	private void conectar() throws Exception {
		Class.forName(driver);
		String sJdbc = "jdbc:sqlite:INAER.sqlite";
		mBD = DriverManager.getConnection(sJdbc);

	}

	/**
	 * Desconexion de base de datos
	 *
	 * @throws Exception
	 */
	public void desconectar() throws Exception {
		mBD.close();
	}

	/**
	 * Metodo de la interfaz CRUD
	 *
	 * @param SQL
	 *            para insertar en la base de datos
	 * @return res
	 * @throws SQLException
	 *             Error por parte de la SQL
	 * @throws Exception
	 */
	public int insert(String SQL) throws SQLException, Exception {
		conectar();
		Statement stmt = mBD.createStatement();
		int res = stmt.executeUpdate(SQL);
		stmt.close();
		desconectar();
		return res;

	}

	/**
	 * Metodo de la interfaz CRUD para la eliminacion en la base de datos
	 *
	 * @param SQL
	 *            Sentencia para la eliminacion
	 * @return int 1 sin errores 0 de lo contrario
	 * @throws SQLException
	 *             Error por parte de la base de datos
	 * @throws Exception
	 */
	public int delete(String SQL) throws SQLException, Exception {
		PreparedStatement stmt = mBD.prepareStatement(SQL);
		int res = stmt.executeUpdate();
		stmt.close();
		desconectar();
		return res;
	}

	/**
	 * Metodo de la interfaz CRUD para la actualizacion de la base de datos
	 *
	 * @param SQL
	 *            Sentencia para la actualizacion
	 * @return int 1 sin errores 0 de lo contrario
	 * @throws SQLException
	 * @throws Exception
	 */
	public int update(String SQL) throws SQLException, Exception {
		conectar();
		Statement stmt = mBD.createStatement();
		int res = stmt.executeUpdate(SQL);
		stmt.close();
		desconectar();
		return res;
	}

	/**
	 *
	 * @param matricula
	 * @return listaReportes lista con los reportes de un determinado aeronave
	 * @throws SQLException
	 *             excepcion generada por la SQL
	 * @throws Exception
	 */
	public Vector<Object> select(TConsulta consulta, String SQL)
			throws SQLException, Exception {
		conectar();
		Statement stmt = mBD.createStatement();
		// Se devuelve
		Vector<Object> salida = new Vector<Object>();
		// Ejecuta
		ResultSet res = stmt.executeQuery(SQL);
		switch (consulta) {
		case IDINCIDENCIAS:
			while (res.next()) {
				int idIncidencias = res.getInt("idincidencia");
				salida.add(idIncidencias);
			}
			break;

		case INCIDENCIAS:
			while (res.next()) {
				int idIncidencias = res.getInt("idincidencia");
				String descripcion = res.getString("descripcion");
				String estado = res.getString("estado");
				String solucion = res.getString("solucion");
				salida.add(idIncidencias);
				salida.add(descripcion);
				salida.add(solucion);
				salida.add(estado);

			}
			break;

		case IDHANGAR:
			while (res.next()) {
				int hangar = res.getInt("id");
				salida.add(hangar);
			}
			break;

		case HANGAR:
			while (res.next()) {
				int idHangar = res.getInt("id");
				String nombre = res.getString("nombre");
				String localizacion = res.getString("localizacion");
				salida.add(idHangar);
				salida.add(nombre);
				salida.add(localizacion);
			}
			break;
		case MATRICULAS:
			while (res.next()) {
				String matricula = res.getString("matricula");
				salida.add(matricula);
			}
			break;
		case AERONAVE:
			while (res.next()) {
				String matricula = res.getString("matricula");
				String modelo = res.getString("modelo");
				int anioFabricacion = res.getInt("añoFabricacion");
				String fechaUltimaRevision = res
						.getString("fechaUltimaRevision");
				String estado = res.getString("estado");
				int id = res.getInt("id");
				salida.add(matricula);
				salida.add(modelo);
				salida.add(anioFabricacion);
				salida.add(fechaUltimaRevision);
				salida.add(estado);
				salida.add(id);
			}
			break;

		case IDREPORTE:
			while (res.next()) {
				int id = res.getInt("idReporte");
				salida.add(id);
			}
			break;
		case REPORTE:
			while (res.next()) {
				String tipo = res.getString("tipo");
				int usuario = res.getInt("usuario");
				int id = res.getInt("idReporte");
				salida.add(usuario);
				salida.add(id);
				salida.add(tipo);
			}
			break;
		}
		stmt.close();
		desconectar();
		return salida;
	}
}
